#region Usings
using System.Collections.Generic;
using System.Data;
using System.Data.SqlClient;
using System.Linq;

using BK.Import.Lib;
#endregion

namespace Import.Lib
{
    public abstract class BaseToDbExpensesImporter<TExpense> : IExpensesImporter
        where TExpense : IExpense
    {
        #region Readonly & Static Fields
        private readonly IDbConnection connection;
        #endregion

        #region C'tors
        protected BaseToDbExpensesImporter(string connectionString)
        {
            connection = new SqlConnection(connectionString);
        }
        #endregion

        #region Instance Methods
        public void Import(IEnumerable<TExpense> expenses)
        {
            connection.Open();
            IDbCommand command = new SqlCommand();
            command.Connection = connection;
            command.CommandText = DoCreateCommandText();
            IDbTransaction transaction = connection.BeginTransaction();
            command.Transaction = transaction;
            try
            {
                foreach (TExpense expense in expenses)
                {
                    command.Parameters.Clear();
                    PutParameterstoCommand(command, expense);
                    command.ExecuteNonQuery();
                }
                transaction.Commit();
            }
            catch
            {
                transaction.Rollback();
            }
            finally
            {
                connection.Close();
            }
        }

        protected abstract string DoCreateCommandText();
        protected abstract void PutParameterstoCommand(IDbCommand command, TExpense expenseEntity);
        #endregion

        #region IExpensesImporter Members
        void IExpensesImporter.Import(IEnumerable<IExpense> expenses)
        {
            List<TExpense> expenseList = expenses.Select(expense => (TExpense) expense).ToList();
            Import(expenseList);
        }
        #endregion
    }
}